/**
 * 
 */
package npap.cater.unr.edu.client.scaffold.place.customized;

import npap.cater.unr.edu.client.managed.request.ApplicationRequestFactory;
import npap.cater.unr.edu.client.proxy.ProjectProxy;
import npap.cater.unr.edu.client.scaffold.place.ProxyListPlace;
import npap.cater.unr.edu.client.scaffold.place.ProxyListPlacePicker;
import npap.cater.unr.edu.client.scaffold.place.ProxyPlace;
import npap.cater.unr.edu.client.scaffold.place.ProxyPlace.Operation;
import npap.cater.unr.edu.client.scaffold.place.ProxyPlaceToListPlace;

import com.google.gwt.event.logical.shared.ValueChangeEvent;
import com.google.gwt.event.logical.shared.ValueChangeHandler;
import com.google.gwt.event.shared.EventBus;
import com.google.gwt.event.shared.HandlerRegistration;
import com.google.gwt.place.shared.Place;
import com.google.gwt.place.shared.PlaceChangeEvent;
import com.google.gwt.place.shared.PlaceController;
import com.google.gwt.user.client.ui.HasConstrainedValue;
import com.google.web.bindery.requestfactory.shared.Receiver;

/**
 * @author Hao
 * 
 */
public class ProjectListPlacePicker implements
		ValueChangeHandler<ProjectListPlace>, PlaceChangeEvent.Handler {
	/**
	 * @uml.property  name="view"
	 * @uml.associationEnd  
	 */
	private HasConstrainedValue<ProjectListPlace> view;
	/**
	 * @uml.property  name="placeController"
	 * @uml.associationEnd  multiplicity="(1 1)"
	 */
	private final PlaceController placeController;
	/**
	 * @uml.property  name="appPlaceToProjectListPlace"
	 * @uml.associationEnd  multiplicity="(1 1)"
	 */
	private final AppPlaceToProjectListPlace appPlaceToProjectListPlace;
	/**
	 * @uml.property  name="requests"
	 * @uml.associationEnd  multiplicity="(1 1)"
	 */
	private final ApplicationRequestFactory requests;

	public ProjectListPlacePicker(PlaceController placeController,
			AppPlaceToProjectListPlace appPlaceToProjectListPlace,
			ApplicationRequestFactory requests) {
		this.placeController = placeController;
		this.appPlaceToProjectListPlace = appPlaceToProjectListPlace;
		this.requests = requests;
	}

	public void onPlaceChange(PlaceChangeEvent event) {
		if ((event.getNewPlace() instanceof ProjectListPlace))
			view.setValue((ProjectListPlace) event.getNewPlace());
		if (event.getNewPlace() instanceof AppPlace) {
			AppPlace newPlace = (AppPlace) event.getNewPlace();
			ProjectListPlace place = new ProjectListPlace(
					newPlace.getProjectID(), newPlace.getProjectName());
			view.setValue(place);
		}
//
//		if (event.getNewPlace() instanceof ProjectPlace) {
//			Place currentPlace = placeController.getWhere();
//			view.setValue((ProjectListPlace) projectPlaceToListPlace
//					.projectListPlaceFor(event.getNewPlace()));
//		}

		// subView.setValue(((ProjectListPlace)event.getNewPlace()).getProxyListPlace());

	}

	public void onValueChange(ValueChangeEvent<ProjectListPlace> event) {
		final ProjectListPlace newProjectListPlace = event.getValue();
		requests.projectRequest()
				.findProject(newProjectListPlace.getIdProject())
				.fire(new Receiver<ProjectProxy>() {

					@Override
					public void onSuccess(ProjectProxy response) {
						// TODO Auto-generated method stub
						AppPlace appPlace = new AppPlace(response.stableId(),
								Operation.DETAILS, newProjectListPlace
										.getIdProject(), newProjectListPlace
										.getProjectName());
						placeController.goTo(appPlace);
					}

				});
	}

	public HandlerRegistration register(EventBus eventBus,
			HasConstrainedValue<ProjectListPlace> view) {
		this.view = view;
		final HandlerRegistration placeRegistration = eventBus.addHandler(
				PlaceChangeEvent.TYPE, this);
		final HandlerRegistration viewRegistration = view
				.addValueChangeHandler(this);

		return new HandlerRegistration() {
			public void removeHandler() {
				placeRegistration.removeHandler();
				viewRegistration.removeHandler();
				ProjectListPlacePicker.this.view = null;
			}
		};
	}

	public HasConstrainedValue<ProjectListPlace> getView() {
		return view;
	}

	public void setView(HasConstrainedValue<ProjectListPlace> view) {
		this.view = view;
	}

	/**
	 * @return
	 * @uml.property  name="placeController"
	 */
	public PlaceController getPlaceController() {
		return placeController;
	}

	/**
	 * @return
	 * @uml.property  name="appPlaceToProjectListPlace"
	 */
	public AppPlaceToProjectListPlace getAppPlaceToProjectListPlace() {
		return appPlaceToProjectListPlace;
	}

	/**
	 * @return
	 * @uml.property  name="requests"
	 */
	public ApplicationRequestFactory getRequests() {
		return requests;
	}

}